package com.app.base.service.auth.service.impl;

import com.app.base.config.exception.SaaSException;
import com.app.base.model.dto.RegisterPageDto;
import com.app.base.model.vo.UsCoVo;
import com.app.base.service.auth.entity.SysUser;
import com.app.base.service.auth.mapper.SysUserMapper;
import com.app.base.service.auth.service.SysUserService;
import com.app.base.service.core.company.entity.Company;
import com.app.base.service.core.company.service.CompanyService;
import com.app.base.utlis.auth.JwtHelper;
import com.app.base.utlis.encryption.MD5Utils;
import com.app.base.utlis.result.Result;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import io.jsonwebtoken.Claims;
import io.jsonwebtoken.Jws;
import io.jsonwebtoken.Jwts;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.BeanUtils;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.stereotype.Service;
import org.springframework.util.StringUtils;

import javax.annotation.Resource;
import javax.servlet.http.HttpServletRequest;
import java.util.Objects;

/**
 * auth
 * @author yuhag
 * @since 2022-05-07
 */
@Service
@Slf4j
public class SysUserServiceImpl extends ServiceImpl<SysUserMapper,SysUser> implements SysUserService {


    @Resource
    private CompanyService companyService;

    @Resource
    private SysUserService userService;

    @Resource
    private RedisTemplate<String,String> redisTemplate;

    @Override
    public Result login(SysUser user) {
        try {

            SysUser sysUser = getOne(new QueryWrapper<SysUser>().eq("username", user.getUsername()).eq("status",0));
            if (Objects.isNull(sysUser)){
                throw new SaaSException("用户名不存在");
            }

            String code = user.getCode();
            Company company = companyService.getById(sysUser.getCompanyId());
            String companyCode = company.getCode();
            if (!code.equals(companyCode)){
                throw new SaaSException("企业账号编号错误！");
            }

            if (!sysUser.getPassword().equals(MD5Utils.encrypt(user.getPassword()))){
                throw new SaaSException("密码不正确,请重新输入");
            }
            String token = JwtHelper.getJwtToken(sysUser.getId(), sysUser.getName());
            return Result.ok().data("token",token);
        }catch (Exception e) {
            log.error(e.getMessage());
            return Result.error(e.getMessage());
        }
    }

    @Override
    public Result info(String token) {
        try {
            String id = JwtHelper.getIdByJwtToken(token);
            SysUser user = getById(id);
            return Result.ok().data("user",user);
        }catch (Exception e) {
            log.error(e.getMessage());
            return Result.error(e.getMessage());
        }
    }

    @Override
    public Result getToken() {
        try{
            SysUser sysUser = baseMapper.selectList(null).get(0);
            String token = JwtHelper.getJwtToken(sysUser.getId(), sysUser.getName());
            return Result.ok(token);
        }catch(Exception e){
            log.error(e.getMessage());
            return Result.error(e.getMessage());
        }
    }

    @Override
    public String getCompanyId(String userId) {
        try{
            return baseMapper.selectById(userId).getCompanyId();
        }catch(Exception e){
            log.error(e.getMessage());
            throw new SaaSException(e.getMessage());
        }
    }

    @Override
    public Result register(RegisterPageDto registerPageDto) {
        try{
            String verificationCode = registerPageDto.getVerificationCode();
            String actualCode = redisTemplate.opsForValue().get(registerPageDto.getPhone());
            if (StringUtils.isEmpty(actualCode)){
                throw new SaaSException("验证码已过期");
            }
            if (!actualCode.equalsIgnoreCase(verificationCode)){
                throw new SaaSException("验证码错误");
            }
            String code = registerPageDto.getCode();
            Company company = companyService.getOne(new LambdaQueryWrapper<Company>()
                    .eq(Company::getCode, code));

            if (Objects.isNull(company)){
                throw new SaaSException("企业编号不存在");
            }
            SysUser user = userService.getOne(new LambdaQueryWrapper<SysUser>()
                    .eq(SysUser::getUsername, registerPageDto.getUsername()));

            if (!Objects.isNull(user)){
                throw new SaaSException("账号已存在！");
            }

            if (!registerPageDto.getPawOne().equals(registerPageDto.getPawTwo())){
                throw new SaaSException("两次密码不一致");
            }
            user = new SysUser();
            BeanUtils.copyProperties(registerPageDto, user);
            user.setCompanyId(company.getId());
            user.setStatus(0);
            user.setPassword(MD5Utils.encrypt(registerPageDto.getPawOne()));
            userService.save(user);
            return Result.ok().message("注册成功!");
        }catch(Exception e){
            log.error(e.getMessage());
            return Result.error(e.getMessage());
        }
    }


    public UsCoVo getUserCompanyInfo(HttpServletRequest request) {
        String jwtToken = request.getHeader("token");
        if (StringUtils.isEmpty(jwtToken)) return null;
        Jws<Claims> claimsJws = Jwts.parser().setSigningKey(JwtHelper.APP_SECRET).parseClaimsJws(jwtToken);
        Claims claims = claimsJws.getBody();
        String userId =  (String) claims.get("id");
        SysUser user = getById(userId);
        String companyId = user.getCompanyId();
        return new UsCoVo(userId,companyId);
    }
}
